/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package org.ipti.br.tag.pdf;

import com.itextpdf.text.BaseColor;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Font;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.pdf.PdfWriter;
import org.ipti.br.tag.entity.Discipline;
import org.ipti.br.tag.entity.Organization;
import org.ipti.br.tag.entity.WorkTopic;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.Normalizer;
import java.util.List;
import java.util.logging.Level;
import javax.ejb.Stateless;
import javax.faces.context.ExternalContext;
import javax.faces.context.FacesContext;
import javax.servlet.http.HttpServletResponse;
import org.ipti.br.tag.util.LoggerUtil;
import org.ipti.br.tag.util.ServiceUtil;

/**
 *
 * @author luancorumba
 */
@Stateless
public class WorkTopicsPDF {
    private static final int DEFAULT_BUFFER_SIZE = 10240;
    private Font catFont = new Font(Font.FontFamily.TIMES_ROMAN, 18, Font.BOLD);
    private Font redFont = new Font(Font.FontFamily.TIMES_ROMAN, 12, Font.NORMAL, BaseColor.RED);
    private Font subFont = new Font(Font.FontFamily.TIMES_ROMAN, 16, Font.BOLD);
    private Font smallBold = new Font(Font.FontFamily.TIMES_ROMAN, 12, Font.BOLD);
    private FacesContext facesContext;
    private ExternalContext externalContext;
    private Organization organization;
    private Discipline discipline;

    public void generate(FacesContext facesContext, List<WorkTopic> roots, Organization org, Discipline discipline){
        this.organization = org;
        this.discipline = discipline;
        
        String name = "Planejamento-"+org.getName()+((discipline != null) ? "-"+discipline.getName() : "");
        name = Normalizer.normalize(name, Normalizer.Form.NFD);
        name = name.replaceAll("[\\W]", "");
        
        facesContext = ServiceUtil.getFacesContext();
        externalContext = facesContext.getExternalContext();
        
        String path = externalContext.getRealPath("resources/pdf/"+name+".pdf");
        
        this.make(path, roots);
        this.send(facesContext,path);
    }
    
    private void make(String file, List<WorkTopic> roots) {
        try {
            Document document = new Document();
            PdfWriter.getInstance(document, new FileOutputStream(file));
            document.open();
            addMetaData(document);
            addTitle(document);
            document.add(recursionList(roots));
            document.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    
    private void addMetaData(Document document) {
        document.addTitle("Cardápio de Atividades");
        document.addSubject("Planejamento Anual");
        document.addKeywords("Planejamento, Atividade, Work, WorkTopic, TAG, IPTI");
        document.addAuthor("Instituto de Pesquisa em Tecnologia e Inovação - IPTI");
        document.addCreator("Tecnologia de Apoio a Gestão - TAG");
    }

    private void addTitle(Document document) throws DocumentException {
        Paragraph preface = new Paragraph();
        Paragraph title = new Paragraph("Prefeitura de Santa Luzia do Itanhi", catFont);
        title.setAlignment(Paragraph.ALIGN_CENTER);
        preface.add(title);

        addEmptyLine(preface, 1);
        Paragraph subTitle = new Paragraph("Planejamento de Atividades", subFont);
        subTitle.setAlignment(Paragraph.ALIGN_CENTER);
        preface.add(subTitle);
        
        Paragraph desc = new Paragraph(organization.getName()+((discipline != null) ? " - "+discipline.getName() : ""), subFont);
        desc.setAlignment(Paragraph.ALIGN_CENTER);
        preface.add(desc);
        
        addEmptyLine(preface, 1);
        preface.add(new Paragraph("A lista a seguir se encontra na seguinte forma: "
                + "\"Código\" - \"Nome da atividade\"", smallBold));

        addEmptyLine(preface, 1);
        document.add(preface);
    }
    
    private com.itextpdf.text.List recursionList(List<WorkTopic> list){
        com.itextpdf.text.List result = new com.itextpdf.text.List(false, false, 10);
        for (WorkTopic workTopic : list) {
            String code;
            if (workTopic.getCode() != null && workTopic.getCode() != 0) {
                code = workTopic.getCode() + " - ";
            } else {
                code = "";
            }
            result.add(code+ workTopic.getName());
            if(workTopic.getSons() != null){
                result.add(recursionList(workTopic.getSons()));
            }
        }
        return result;
    }

    private void addEmptyLine(Paragraph paragraph, int number) {
        for (int i = 0; i < number; i++) {
            paragraph.add(new Paragraph(" "));
        }
    }
    
    private void send(FacesContext facesContext, String path){
        HttpServletResponse response = (HttpServletResponse) externalContext.getResponse();

        File file = new File(path);
        BufferedInputStream input = null;
        BufferedOutputStream output = null;

        try {
            input = new BufferedInputStream(new FileInputStream(file), DEFAULT_BUFFER_SIZE);
            response.reset();
            response.setHeader("Content-Type", "application/pdf");
            response.setHeader("Content-Length", String.valueOf(file.length()));
            response.setHeader("Content-Disposition", "inline; filename=\"" + file.getName() + "\"");
            output = new BufferedOutputStream(response.getOutputStream(), DEFAULT_BUFFER_SIZE);
            byte[] buffer = new byte[DEFAULT_BUFFER_SIZE];
            int length;
            while ((length = input.read(buffer)) > 0) {
                output.write(buffer, 0, length);
            }
            output.flush();
        } catch (Exception ex) {
            ex.printStackTrace();
            LoggerUtil.log("SimpleFrequencyBean:export", Level.SEVERE, "Não enviou", ex);
        } finally {
            try {
                output.close();
                input.close();
            } catch (IOException e) {
                e.printStackTrace();
                LoggerUtil.log("SimpleFrequencyBean:export", Level.SEVERE, "Não fechou", e);
            }
        }
        facesContext.responseComplete();
        file.delete();
    }
}